package org.hyn.gateway.bind;

import org.hyn.gateway.mapping.HttpStatement;
import org.hyn.gateway.session.Configuration;
import org.hyn.gateway.session.GatewaySession;

import java.util.HashMap;
import java.util.Map;

/**
 * @author franyhu
 * @description 映射注册器
 * @date 2025/3/3
 */
public class MapperRegistry {

    private final Configuration configuration;

    public MapperRegistry(Configuration configuration) {
        this.configuration = configuration;
    }

    // 泛化调用静态代理工厂
    private final Map<String, MapperProxyFactory> knownMappers = new HashMap<String, MapperProxyFactory>();

    /**
     * 获取工厂后，并进行实例化
     * @param uri URI
     * @param session 会话
     * @return 泛化调用实例
     */
    public IGenericReference getMapper(String uri, GatewaySession session) {
        final MapperProxyFactory mapperProxyFactory = knownMappers.get(uri);
        if (mapperProxyFactory == null) {
            throw new RuntimeException("Uri " + uri + " is not known to the MapperRegistry.");
        }
        try {
            return mapperProxyFactory.newInstance(session);
        } catch (Exception e) {
            throw new RuntimeException("Error getting mapper instance. Cause: " + e, e);
        }
    }

    /**
     * 向mapper中添加
     * @param httpStatement 网关接口信息
     */
    public void addMapper(HttpStatement httpStatement) {
        String uri = httpStatement.getUri();
        // 如果重复注册则报错
        if (hasMapper(uri)) {
            throw new RuntimeException("Uri " + uri + " is already know to the MapperRegistry.");
        }
        knownMappers.put(uri, new MapperProxyFactory(uri));
        // 保存接口映射信息
        configuration.addHttpStatement(httpStatement);
    }

    public Boolean hasMapper(String uri) {
        return knownMappers.containsKey(uri);
    }
}
